package gateway.mgt

import com.amihaiemil.camel.Yaml
import gateway.mgt.api.ApiConstantParam
import gateway.mgt.api.ApiDefinition
import gateway.mgt.api.ApiGroup
import grails.testing.gorm.DomainUnitTest
import spock.lang.Specification

class ApiConstantParamSpec extends Specification implements DomainUnitTest<ApiConstantParam> {

    static final ApiGroup apiGroupInstance = new ApiGroup(name: "default")

    static final ApiDefinitionProperties = [
            apiGroup: apiGroupInstance, name: "demo1", description: "demo api 1",
            request : [path: "/Service-Set-1/sampleApi1"], backend: [host: "lb://Service-Set-1", path: "/sampleApi1"]
    ]

    static final ApiDefinition apiDefinitionInstance = new ApiDefinition(ApiDefinitionProperties)

    static final ValidPropertiesSet = [
            [
                    apiDefinition: apiDefinitionInstance, order: 1, description: "a demo constant parameter1",
                    type         : ApiConstantParam.Type.String,
                    scope        : ApiConstantParam.Scope.Header,
                    name         : "op1", value: "Hello world"
            ],
            [
                    apiDefinition: apiDefinitionInstance, order: 2, description: "a demo constant parameter2",
                    type         : ApiConstantParam.Type.Integer, scope: ApiConstantParam.Scope.Path,
                    name         : "op2", value: "12345"
            ]
    ]

    static final InvalidPropertiesSet = [
            [
                    order                 : 1, type: ApiConstantParam.Type.String, name: "op1",
                    expected_error_counter: 3
            ],
            [
                    apiDefinition         : apiDefinitionInstance, order: -2, type: ApiConstantParam.Type.Integer,
                    scope                 : ApiConstantParam.Scope.Path, name: "op2",
                    expected_error_counter: 2
            ]
    ]

    def setupSpec() {
        apiGroupInstance.save(flush: true)
        apiDefinitionInstance.save(flush: true)
    }

    def setup() {
    }

    def cleanup() {
    }

    void "test a valid properties"() {
        given:
        def instance = new ApiConstantParam(params)

        when:
        instance.save(flush: true)

        then:
        !instance.hasErrors()

        where:
        params << ValidPropertiesSet
    }

    void "test an invalid properties"() {
        given:
        def instance = new ApiConstantParam(params)

        when:
        instance.save(flush: true)

        then:
        instance.hasErrors()

        and:
        instance.errors.allErrors.size() == params.expected_error_counter

        where:
        params << InvalidPropertiesSet
    }

    void "test method: 'Pluggable#plug(Map)' of the instance for 'add a constant parameter in headers'"() {
        given:
        def params = [
                apiDefinition: apiDefinitionInstance, order: 1, description: "add a constant parameter",
                type         : ApiConstantParam.Type.String,
                scope        : ApiConstantParam.Scope.Header,
                name         : "op1", value: "Hello world"
        ]
        def paramsBuilder = [filters: Yaml.createYamlSequenceBuilder(), predicates: Yaml.createYamlSequenceBuilder()]

        when:
        new ApiConstantParam(params).save(flush: true).plug(paramsBuilder)

        and:
        def parts = paramsBuilder.filters.build().toString().split("=")
        def subparts = parts[1].split(",")

        then:
        parts.size() == 2
        parts[0] == "- AddRequestHeader"

        and:
        subparts[0] == params.name
        subparts[1].trim() == params.value
    }
}
